package com.guguskins.back.utils.pay;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.guguskins.back.utils.CommonUtil;
import com.guguskins.back.utils.DateUtil;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.client.RestTemplate;

import java.util.*;

public class Unionpay {

    public final static String MSG_SRC_ID = "3194";

    public static void main(String[] args) {
        System.err.println(pay(CommonUtil.generateSn(MSG_SRC_ID), DateUtil.getDate("yyyy-MM-dd"), 1, ""));
    }

    /**
     * 下单
     *
     * @param billNo      订单号（{来源编号(4位)}{时间(yyyyMMddmmHHssSSS)(17位)}{7位随机数}）
     * @param billDate    订单日期（格式：yyyy-MM-dd）
     * @param totalAmount 支付金额（单位：分）
     */
    public static JSONObject pay(String billNo, String billDate, int totalAmount, String uri) {
        String urlParam = "https://qr-test2.chinaums.com/netpay-route-server/api/";
        //  封装参数，千万不要替换为Map与HashMap，否则参数无法传递
//        JSONObject postData = new JSONObject();
        Map<String, Object> postData = new HashMap<>();
        //  也支持中文
        postData.put("msgType", "bills.getQRCode");
        postData.put("mid", "898340149000005");
        postData.put("tid", "88880001");
        postData.put("instMid", "QRPAYDEFAULT");
        postData.put("signType", "SHA256");

        postData.put("msgSrc", "WWW.TEST.COM");
        String requestTimestamp = DateUtil.getDate("yyyy-MM-dd HH:mm:ss");
        postData.put("requestTimestamp", requestTimestamp);
        postData.put("totalAmount", totalAmount);

        // billNo、billDate
        //{来源编号(4位)}{时间(yyyyMMddmmHHssSSS)(17位)}{7位随机数}
        postData.put("billNo", billNo);
        postData.put("billDate", billDate);

        //后端回调地址
        postData.put("notifyUrl", uri + "/api/thirdCallback/unionpay");
        System.err.println(uri + "/api/thirdCallback/unionpay");
        //前端跳转页面
//        postData.put("returnUrl", uri + "");

        String strEncode = getSignToken(postData) + "fcAmtnx7MwismjWNhNKdHC44mNXtnEQeJkRrhKJwyrW2ysRR";
        postData.put("sign", SHAUtils.getSHA256StrJava(strEncode));

        RestTemplate client = new RestTemplate();
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        HttpEntity<String> request = new HttpEntity<>(JSON.toJSONString(postData), headers);
        ResponseEntity<JSONObject> postForEntity = client.postForEntity(urlParam, request, JSONObject.class);

        return postForEntity.getBody();
        /*JSONObject body = postForEntity.getBody();
        assert body != null;
        System.out.println(body.toJSONString());*/
    }

    /**
     * 查询账单状态
     */
    public static JSONObject query(String billNo, String billDate, int refundAmount) {
        String urlParam = "https://qr-test2.chinaums.com/netpay-route-server/api/";
        //  封装参数，千万不要替换为Map与HashMap，否则参数无法传递
//        JSONObject postData = new JSONObject();
        Map<String, Object> postData = new HashMap<>();
        //  也支持中文
        postData.put("msgType", "bills.query");
        postData.put("mid", "898340149000005");
        postData.put("tid", "88880001");
        postData.put("instMid", "QRPAYDEFAULT");
        postData.put("signType", "SHA256");

        postData.put("msgSrc", "WWW.TEST.COM");
        String requestTimestamp = DateUtil.getDate("yyyy-MM-dd HH:mm:ss");
        postData.put("requestTimestamp", requestTimestamp);
        postData.put("refundAmount", refundAmount);

        // billNo、billDate
        //{来源编号(4位)}{时间(yyyyMMddmmHHssSSS)(17位)}{7位随机数}
        postData.put("billNo", billNo);
        postData.put("billDate", billDate);

        String strEncode = getSignToken(postData) + "fcAmtnx7MwismjWNhNKdHC44mNXtnEQeJkRrhKJwyrW2ysRR";
        postData.put("sign", SHAUtils.getSHA256StrJava(strEncode));

        RestTemplate client = new RestTemplate();
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        HttpEntity<String> request = new HttpEntity<>(JSON.toJSONString(postData), headers);
        ResponseEntity<JSONObject> postForEntity = client.postForEntity(urlParam, request, JSONObject.class);

        return postForEntity.getBody();
        /*JSONObject body = postForEntity.getBody();
        assert body != null;
        System.out.println(body.toJSONString());*/
    }


    public static JSONObject refund(String billNo, String billDate, int refundAmount) {
        String urlParam = "https://qr-test2.chinaums.com/netpay-route-server/api/";
        //  封装参数，千万不要替换为Map与HashMap，否则参数无法传递
//        JSONObject postData = new JSONObject();
        Map<String, Object> postData = new HashMap<>();
        //  也支持中文
        postData.put("msgType", "bills.refund");
        postData.put("mid", "898340149000005");
        postData.put("tid", "88880001");
        postData.put("instMid", "QRPAYDEFAULT");
        postData.put("signType", "SHA256");

        postData.put("msgSrc", "WWW.TEST.COM");
        String requestTimestamp = DateUtil.getDate("yyyy-MM-dd HH:mm:ss");
        postData.put("requestTimestamp", requestTimestamp);
        postData.put("refundAmount", refundAmount);

        // billNo、billDate
        //{来源编号(4位)}{时间(yyyyMMddmmHHssSSS)(17位)}{7位随机数}
        postData.put("billNo", billNo);
        postData.put("billDate", billDate);

        String strEncode = getSignToken(postData) + "fcAmtnx7MwismjWNhNKdHC44mNXtnEQeJkRrhKJwyrW2ysRR";
        postData.put("sign", SHAUtils.getSHA256StrJava(strEncode));

        RestTemplate client = new RestTemplate();
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        HttpEntity<String> request = new HttpEntity<>(JSON.toJSONString(postData), headers);
        ResponseEntity<JSONObject> postForEntity = client.postForEntity(urlParam, request, JSONObject.class);

        return postForEntity.getBody();
        /*JSONObject body = postForEntity.getBody();
        assert body != null;
        System.out.println(body.toJSONString());*/
    }

    private static void sendRequest() {

    }

    /**
     * 生成签名
     *
     * @param map
     * @return
     */
    private static String getSignToken(Map<String, Object> map) {
        List<Map.Entry<String, Object>> infoIds = new ArrayList<>(map.entrySet());
        // 对所有传入参数按照字段名的 ASCII 码从小到大排序（字典序）
        infoIds.sort(Map.Entry.comparingByKey());
        // 构造签名键值对的格式
        StringBuilder sb = new StringBuilder();
        for (Map.Entry<String, Object> item : infoIds) {
            String key = item.getKey();
            String val = String.valueOf(item.getValue());
            if (!("".equals(val) || val == null)) {
                sb.append(key).append("=").append(val).append("&");
            }
        }
        return sb.substring(0, sb.length() - 1);
//        return sb.toString();
        //进行MD5加密
    }
}
